﻿#include "kernel_list_service.h"

// 初始化客户端节点
client_node *init_client_node() {
    client_node *head = (client_node *)malloc(sizeof (client_node));
    if (head == NULL)
        return (void *)0;
    memset(head, 0, sizeof (client_node));
    INIT_LIST_HEAD(&head->list);
    return head;
}

// 获取一个客户端节点
client_node *get_client_node(char *name, int client_fd, char *ip, int port) {
    client_node *new = init_client_node();
    strcpy(new->name, name);
    new->client_fd = client_fd;
    strcpy(new->ip, ip);
    new->port = port;
    return new;
}

// 尾插一个客户端节点
int insert_client(client_node *client_head, client_node *new_client) {
    list_add_tail(&client_head->list, &new_client->list);  // 入链
    return 0;
}

// 释放客户端链表所有内存,头节点除外
void destroy_client(client_node *client_head) {
    client_node *p = NULL;
    struct list_head *pos = NULL;
    struct list_head *n = NULL;
    list_for_each_safe(pos, n, &client_head->list) {
        p = list_entry(pos, client_node, list);
        free(p);
        p = NULL;
    }
    INIT_LIST_HEAD(&client_head->list);
}

// 打印所有客户端链表
void display_all_client(client_node *client_head) {
    client_node *tmp = NULL;
    printf("名称\t文件描述符\tIP地址\t端口号\n");
    list_for_each_entry(tmp, &client_head->list, list) {
        printf("%s\t", tmp->name);
        printf("%d\t", tmp->client_fd);
        printf("%s\t", tmp->ip);
        printf("%d\n", tmp->port);
    }
}

// 打印一个客户端节点
void display_one_client(client_node *client) {
    printf("名称\t文件描述符\tIP地址\t端口号\n");
    printf("%s\t", client->name);
    printf("%d\t", client->client_fd);
    printf("%s\t", client->ip);
    printf("%d\n", client->port);
}

// 根据名称查找客户端节点
client_node *search_client_by_name(client_node *client_head, char *name) {
    client_node *tmp = NULL;
    // 遍历寻找指定account的节点
    list_for_each_entry(tmp, &client_head->list, list) {
        if (0 == strcmp(tmp->name, name)) { // 找到同名
            return tmp;
        }
    }
    return NULL;
}

// 根据文件描述符查找客户端节点
client_node *search_client_by_fd(client_node *client_head, int client_fd) {
    client_node *tmp = NULL;
    // 遍历寻找指定account的节点
    list_for_each_entry(tmp, &client_head->list, list) {
        if (tmp->client_fd == client_fd) { // 找到同名
            return tmp;
        }
    }
    return NULL;
}

// 根据客户端文件描述符删除节点,没找到就不删,成功返回0,失败返回-1
int delete_client(client_node *client_head, int client_fd) {
    client_node *tmp = NULL;
    tmp = search_client_by_fd(client_head, client_fd);  // find target node
    if (tmp == NULL) {
        printf("there is no such client\n");
        return -1;
    } else {
        list_del(&tmp->list);
        free(tmp);
        tmp = NULL;
    }
    return 0;
}

// 获取链表大小
int get_client_count(client_node *client_head) {
    int count = 0;
    client_node *tmp = NULL;
    // 遍历寻找指定account的节点
    list_for_each_entry(tmp, &client_head->list, list) {
        count++;
    }
    return count;
}